/*
 * prop.c
 *
 *  Created on: 2011-08-16
 *      Author: Baron Wang
 */


#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define LINE_BUF   200
#define PROP_SIZE  48

/*
 * A simple properties reader.
 */

static FILE        *__f;
static int         __line;

int init_properties(const char* file){

    if(NULL == file){
        printf("NULL pointer.\n");
        return -1;
    }

    __f = fopen(file, "r");

    if(NULL == __f){
        printf("fail to open file %s.", file);
        return -1;
    }

    return 0;
}

void fini_properties(){
    fclose(__f);
    __line = 0;
}

static int trim_begin(char *value){

    register char *ptr;

    if((*value == ' ') || (*value == '\t')){
        ptr = value;
        do{
            ++ptr;
        } while((*ptr == ' ') || (*ptr == '\t'));

        strcpy(value, ptr);
    }

    /* for the stupid windows */
    if(*value == '\r' || *value == '\n'){
        return 1;
    }

    if(*value == '#' || *value == '\0'){
        return 1;
    }
    return 0;
}

static char* trim_end(char* value){

    register char *ptr;
    register int len;

    len = strlen(value);
    if((value[len - 1] == ' ') || (value[len - 1] == '\t')){
        ptr = value + len - 1;
        do{
            --ptr;
        } while((*ptr == ' ') || (*ptr == '\t'));

        *(ptr + 1) = '\0';
    }
    return value;
}

int read_config_num(const char* field, int def){

    char name[PROP_SIZE] = {0};
    char value[PROP_SIZE] = {0};
    char linebuf[LINE_BUF];

    if(NULL == field){
        printf("NULL pointer.\n");
        return def;
    }

reread:
    if(NULL == fgets(linebuf, LINE_BUF, __f)){
        printf("the end of file, use default.");
        return def;
    }

    ++__line;
    if(trim_begin(linebuf)){
        goto reread;
    }

    trim_end(linebuf);

    if(2 != sscanf(linebuf, "%s = %s", name, value)){
        printf("ERROR: invalid attribute value pair at line %d, "
            "should be \"<attribute> = <value>\".\n", __line);
        return def;
    }

    if(strcmp(name, field)){
        printf("ERROR: %s expected at line %d.\n", field, __line);
        return def;
    }

    return atoi(value);
}

char* read_config_value(char* field, char* resbuf, const char* def){

    char name[PROP_SIZE] = {0};
    char value[PROP_SIZE] = {0};
    char linebuf[LINE_BUF];

    if(NULL == field){
        printf("NULL pointer.\n");
        return (char*)def;
    }

reread:
    if(NULL == fgets(linebuf, LINE_BUF, __f)){
        printf("the end of file, use default.");
        return (char*)def;
    }

    ++__line;
    if(trim_begin(linebuf)){
        goto reread;
    }

    trim_end(linebuf);

    if(2 != sscanf(linebuf, "%s = %s", name, value)){
        printf("ERROR: invalid attribute value pair at line %d, "
            "should be \"<attribute> = <value>\"\n", __line);
        return (char*)def;
    }

    if(strcmp(name, field)){
        printf("ERROR: %s expected at line %d\n", field, __line);
        return (char*)def;
    }

    if(0 == strcmp("NULL", value)){
        return (char*)def;
    }else{
        strcpy(resbuf, value);
    }

    return resbuf;
}

